package com.atjinggu.jinggumail.search.thread;

import java.util.concurrent.*;

/**
 * @author jingming
 * @Type CompletableFutureTest.java
 * @Desc
 * @date 2021/2/17 15:22
 */
public class CompletableFutureTest {
    public static ExecutorService executor = Executors.newFixedThreadPool(10);

    public static void main(String[] args) throws ExecutionException, InterruptedException {


//        CompletableFuture.runAsync(()->{
//            System.out.println("当前线程Id ********* " + Thread.currentThread().getId());
//            int i = 10 / 2;
//        },executor);

//        CompletableFuture<Integer> future = CompletableFuture.supplyAsync(() -> {
//            System.out.println("当前线程Id ********* " + Thread.currentThread().getId());
//            int i = 10 / 2;
//            return i;
//        }, executor);
//        Integer integer = future.get();
//        future.whenComplete()
//        System.out.println("主线程开始执行********");
//        CompletableFuture<Integer> fu = CompletableFuture.supplyAsync(() -> {
//            System.out.println("当前线程Id ********* " + Thread.currentThread());
//            int i = 10 / 0;
//            return i;
//        },executor).whenCompleteAsync((u,exception) -> {
//            System.out.println("当前线程Id ********* " + Thread.currentThread());
//            System.out.println(u);
//            System.out.println(exception);
//        }).exceptionally( exception -> {
//            System.out.println("异常 -》 "+exception);
//            return 0;
//        });
//        CompletableFuture<Integer> fu = CompletableFuture.supplyAsync(() -> {
//            System.out.println("当前线程Id ********* " + Thread.currentThread());
//            int i = 10 / 1;
//            return i;
//        },executor).whenCompleteAsync((x,y)-> {
//            System.out.println("whenComplate");
//        },executor).handleAsync((x,y) -> {
//            System.out.println("handle");
//            System.out.println(x);
//            System.out.println(y);
//            return 0;
//        },executor).exceptionally(x -> {
//            System.out.println("异常了");
//            return 1;
//        });
//        Integer integer = fu.get();
//        System.out.println(integer);
//        System.out.println(Thread.currentThread().getId());
//        System.out.println("主线程开始执行********");
//        CompletableFuture<Integer> future = CompletableFuture.supplyAsync(() -> {
//            System.out.println("当前线程Id ********* " + Thread.currentThread().getId());
//            int i = 10 / 1;
//            return i;
//        }, executor).thenApplyAsync((result) -> {
//            System.out.println("then Run ****" + result);
//            return result;
//        });
//        Integer integer = future.get();
//        System.out.println(integer);
//        System.out.println("主线程执行结束********");

        /**
         * 两任务都要完成
         */
//        System.out.println("主线程开始执行********");
//        CompletableFuture<Integer> future01 = CompletableFuture.supplyAsync(() -> {
//            System.out.println("任务1开始Id ********* " + Thread.currentThread().getName());
//            try {
//                TimeUnit.MILLISECONDS.sleep(1000);
//            } catch (InterruptedException e) {
//                e.printStackTrace();
//            }
//            int i = 10 / 1;
//            System.out.println("任务1结束!");
//            return i;
//        }, executor);
//
//        CompletableFuture<String> future02 = CompletableFuture.supplyAsync(() -> {
//            System.out.println("任务2开始Id ********* " + Thread.currentThread().getName());
//            try {
//                TimeUnit.MILLISECONDS.sleep(100);
//            } catch (InterruptedException e) {
//                e.printStackTrace();
//            }
//            System.out.println("任务2结束!");
//            return "Hello!";
//        }, executor);
//
//        future01.runAfterBothAsync(future02,()-> {
//            System.out.println("任务3开始Id ********* " + Thread.currentThread().getName());
//            System.out.println("任务3结束!");
//        },executor);
//        System.out.println("主线程执行结束********");
        //executor.shutdown();

//        System.out.println("主线程开始执行********");
//        CompletableFuture<Integer> future01 = CompletableFuture.supplyAsync(() -> {
//            System.out.println("任务1开始Id ********* " + Thread.currentThread().getName());
//            try {
//                TimeUnit.MILLISECONDS.sleep(1000);
//            } catch (InterruptedException e) {
//                e.printStackTrace();
//            }
//            int i = 10 / 1;
//            System.out.println("任务1结束!");
//            return i;
//        }, executor);
//
//        CompletableFuture<Integer> future02 = CompletableFuture.supplyAsync(() -> {
//            System.out.println("任务2开始Id ********* " + Thread.currentThread().getName());
//            try {
//                TimeUnit.MILLISECONDS.sleep(100);
//            } catch (InterruptedException e) {
//                e.printStackTrace();
//            }
//            System.out.println("任务2结束!");
//            return 1;
//        }, executor);

//        future01.runAfterBothAsync(future02,()-> {
//            System.out.println("任务3开始Id ********* " + Thread.currentThread().getName());
//            System.out.println("任务3结束!");
//        },executor);
//        future01.thenAcceptBothAsync(future02,(res1,res2) -> {
//            System.out.println("任务3开始Id ********* " + Thread.currentThread().getName());
//            System.out.println("主线程1结果"+res1);
//            System.out.println("主线程2结果"+res2);
//                System.out.println("任务3结束!");
//        },executor);

//        CompletableFuture<String> future03 = future01.thenCombineAsync(future02, (res1, res2) -> {
//            System.out.println("任务3开始Id ********* " + Thread.currentThread().getName());
//            try {
//                TimeUnit.MILLISECONDS.sleep(100);
//            } catch (InterruptedException e) {
//                e.printStackTrace();
//            }
//            System.out.println("主线程1结果" + res1);
//            System.out.println("主线程2结果" + res2);
//            System.out.println("任务3结束!");
//            return "world!";
//        }, executor);
//        System.out.println("主线程3结果" + future03.get());
//        future01.runAfterEitherAsync(future02,() -> {
//            System.out.println("任务3开始Id ********* " + Thread.currentThread().getName());
//            System.out.println("任务3结束 ********* ");
//        },executor);
//        future01.acceptEitherAsync(future02,(r) -> {
//            System.out.println("任务3开始Id ********* " + Thread.currentThread().getName());
//            System.out.println("上一步结果：r "+r);
//            System.out.println("任务3结束 ********* ");
//        },executor);
//        CompletableFuture<String> future = future01.applyToEitherAsync(future02, (r) -> {
//            System.out.println("任务3开始Id ********* " + Thread.currentThread().getName());
//            System.out.println("上一步结果：r " + r);
//            System.out.println("任务3结束 ********* ");
//            return "xxxx";
//        }, executor);
//        String s = future.get();
//        System.out.println(s);
        CompletableFuture<String> futureImg = CompletableFuture.supplyAsync(() -> {
            System.out.println("查询商品图片信息");
            return "hello.jpg";
        });
        CompletableFuture<String> futureAttr = CompletableFuture.supplyAsync(() -> {
            System.out.println("查询商品属性信息");
            return "黑色+256G";
        });
        CompletableFuture<String> futureDesc = CompletableFuture.supplyAsync(() -> {
            try {
                TimeUnit.MILLISECONDS.sleep(2000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println("查询商品描述信息");
            return "华为";
        });
//        CompletableFuture<Void> future = CompletableFuture.allOf(futureImg, futureAttr, futureDesc);
        CompletableFuture<Object> anyOf = CompletableFuture.anyOf(futureImg, futureAttr, futureDesc);
        //等待所有执行完
        System.out.println("执行最快的："+anyOf.get());
        System.out.println("主线程执行结束********"+futureImg.get() + futureAttr.get()+futureDesc.get());
    }

    public static class Callable01 implements Callable<Integer>{

        @Override
        public Integer call() throws Exception {
            System.out.println("当前线程Id ********* "+Thread.currentThread().getId());
            int i = 10 / 2;
            return i;
        }
    }
}